# -*- coding: utf-8 -*-

"""
@author: 猿小天
@contact: QQ:1638245306
@Created on: 2021/6/6 006 10:30
@Remark: 自定义权限
"""
import re

from django.contrib.auth.models import AnonymousUser
from django.db.models import F
from rest_framework.permissions import BasePermission

from dvadmin.system.models import ApiWhiteList, RoleMenuButtonPermission, Role


def ValidationApi(reqApi, validApi):
    """
    验证当前用户是否有接口权限
    :param reqApi: 当前请求的接口
    :param validApi: 用于验证的接口
    :return: True或者False
    """
    if validApi is not None:
        valid_api = validApi.replace('{id}', '.*?')
        matchObj = re.match(valid_api, reqApi, re.M | re.I)
        if matchObj:
            return True
        else:
            return False
    else:
        return False


class AnonymousUserPermission(BasePermission):
    """
    匿名用户权限
    """

    def has_permission(self, request, view):
        if isinstance(request.user, AnonymousUser):
            return False
        return True


class SuperuserPermission(BasePermission):
    """
    超级管理员权限类
    """

    def has_permission(self, request, view):
        if isinstance(request.user, AnonymousUser):
            return False
        # 判断是否是超级管理员
        if request.user.is_superuser:
            return True


class AdminPermission(BasePermission):
    """
    普通管理员权限类
    """

    def has_permission(self, request, view):
        if isinstance(request.user, AnonymousUser):
            return False
        # 判断是否是超级管理员
        is_superuser = request.user.is_superuser
        # 判断是否是管理员角色
        is_admin = request.user.role.values_list('admin', flat=True)
        if is_superuser or True in is_admin:
            return True


def ReUUID(api):
    """
    将接口的uuid替换掉
    :param api:
    :return:
    """
    pattern = re.compile(r'[a-f\d]{4}(?:[a-f\d]{4}-){4}[a-f\d]{12}/$')
    m = pattern.search(api)
    if m:
        res = api.replace(m.group(0), ".*/")
        return res
    else:
        return None


class CustomPermission(BasePermission):
    """自定义权限"""

    def has_permission(self, request, view):
        if isinstance(request.user, AnonymousUser):
            return False
        # 判断是否是超级管理员（支持 is_superuser 字段和 role_id=1 或 role_key="admin" 两种方式）
        is_superuser = getattr(request.user, 'is_superuser', False)
        # 如果 is_superuser 为 True，直接返回 True
        if is_superuser:
            return True
        # 如果 is_superuser 为 False 或 None，检查角色是否为管理员（通过 role_id=1 或 role_key="admin"）
        if hasattr(request.user, "role"):
            try:
                role_ids = list(request.user.role.values_list('id', flat=True))
                role_keys = list(request.user.role.values_list('key', flat=True))
                # 检查 role_id=1 或 role_key="admin"
                if 1 in role_ids or 'admin' in role_keys:
                    return True
            except Exception as e:
                # 如果查询角色时出错，记录错误但继续检查菜单按钮权限
                import logging
                logger = logging.getLogger(__name__)
                logger.warning(f"检查用户角色时出错: {e}")
        # 如果不是管理员，检查菜单按钮权限
        api = request.path  # 当前请求接口
        method = request.method  # 当前请求方法
        methodList = ['GET', 'POST', 'PUT', 'DELETE', 'OPTIONS', 'PATCH']
        try:
            method = methodList.index(method)
        except ValueError:
            # 如果方法不在列表中，默认使用 GET (index 0)
            method = 0
        # ***接口白名单***
        try:
            api_white_list = ApiWhiteList.objects.values(permission__api=F('url'), permission__method=F('method'))
            api_white_list = [
                str(item.get('permission__api').replace('{id}', '([a-zA-Z0-9-]+)')) + ":" + str(
                    item.get('permission__method')) + '$' for item in api_white_list if item.get('permission__api')]
        except Exception:
            api_white_list = []
        # ********#
        if not hasattr(request.user, "role"):
            return False
        try:
            role_id_list = request.user.role.values_list('id', flat=True)
            userApiList = RoleMenuButtonPermission.objects.filter(role__in=role_id_list).values(
                permission__api=F('menu_button__api'), permission__method=F('menu_button__method'))  # 获取当前用户的角色拥有的所有接口
            ApiList = [
                str(item.get('permission__api').replace('{id}', '([a-zA-Z0-9-]+)')) + ":" + str(
                    item.get('permission__method')) + '$' for item in userApiList if item.get('permission__api')]
        except Exception:
            ApiList = []
        new_api_ist = api_white_list + ApiList
        new_api = api + ":" + str(method)
        for item in new_api_ist:
            matchObj = re.match(item, new_api, re.M | re.I)
            if matchObj is None:
                continue
            else:
                return True
        else:
            return False
